
package guoan.service;

import guoan.core.dto.DataGridModel;
import guoan.core.dto.PageResponse;
import guoan.core.dto.RestResponse;
import guoan.domain.Exam;
import guoan.domain.ExamItemStatus;
import guoan.repository.ExamRepository;

import java.util.Iterator;
import java.util.List;
import java.util.Map;

import org.joda.time.DateTime;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.google.common.base.Preconditions;
import com.google.common.base.Splitter;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;

/**
 * ClassName: ExamService <br/>
 * 预约考试 service <br/>
 * date: 2015年4月13日 下午2:56:18 <br/>
 *
 * @author he.sun
 * @version
 * @since JDK 1.7
 */
@Service
@Transactional
public class ExamService extends PageSerivce<Exam> {
    protected final Logger log = LoggerFactory.getLogger(getClass());

    @Autowired
    private ExamRepository examRepository;

    @Autowired
    private ExamItemStatusService examItemStatusService;
    @Autowired
    private ExamItemService examItemService;
    @Autowired
    private StudentService studentService;

    /**
     * create:创建新的预约考试. <br/>
     * 1.保存 Exam 2.根据 Exam中的开放时间批量增加 ExamItemStatus
     * 
     * @author he.sun
     * @param exam
     * @return
     */
    public Exam create(Exam exam){
        log.info("[新增预约考试]开始");
        exam.setCreateTime(new DateTime());
        exam.setUpdateTime(exam.getCreateTime());
        log.debug("exam befor:{}", exam);
        exam = examRepository.save(exam);
        log.debug("exam afert:{}", exam);

        // 获得那些预约考试的开放时间
        String examOpenHours = Preconditions.checkNotNull(exam.getOpenHours(),
                "请填写预约的开放时间");

        log.debug("exam examOpenHours:{}", examOpenHours);
        Iterator<String> openHoursIter = Splitter.on(",").split(examOpenHours)
                .iterator();

        // 批量生成预约考试时间表
        List<ExamItemStatus> ExamItemStatusList = Lists.newArrayList();
        while (openHoursIter.hasNext()) {
            log.debug("examItemStatus create start ================================");
            // ExamItemStatus
            ExamItemStatus examItemStatus = new ExamItemStatus();
            // 预约总数
            examItemStatus.setApplicantsNumber(0L);
            // 预约考试ID
            examItemStatus.setExamId(exam.getId());
            // 预约时间
            examItemStatus.setOpenHours(Long.valueOf(openHoursIter.next()));
            log.debug("examItemStatus:{}", examItemStatus);
            log.debug("examItemStatus create end   ================================");
            // list add
            ExamItemStatusList.add(examItemStatus);
        }
        /*
         * 批量增加预约考试时间表
         */
        examItemStatusService.create(ExamItemStatusList);
        log.info("[新增预约考试]结束");

        return exam;
    }

    /**
     * add:保存预约考试信息. <br/>
     *
     * @author he.sun
     * @param exam
     * @return
     */
    public RestResponse<Boolean> add(Exam exam){
        exam = create(exam);
        if (exam != null && exam.getId() != null) {
            return RestResponse.ok(true);
        }
        return RestResponse.error("系统错误，请联系系统管理人员");
    }

    public PageResponse<Exam> page(String type, DataGridModel dataGridModel){
        // TODO Auto-generated method stub
        Map<String, Object> paramMap = Maps.newHashMap();
        DateTime nowTime = new DateTime();
        if (type.equals("NOW")) { // 现在时间大于等于开始报名时间 ，小于考试时间是可报名的考试
            paramMap.put("GTE_examTime", new DateTime(nowTime.getYear(),
                    nowTime.getMonthOfYear(), nowTime.getDayOfMonth(), 0, 0, 0));
            paramMap.put("LT_resTime", nowTime);
        } else if (type.equals("LOS")) {// 考试时间小雨现在时间过期的考试
            paramMap.put("LT_examTime",
                    new DateTime(nowTime.getYear(), nowTime.getMonthOfYear(),
                            nowTime.getDayOfMonth(), 0, 0, 0));
        }
        return this.pageResponse(examRepository, paramMap, dataGridModel);
    }

    public boolean exists(Long examId){
        // TODO Auto-generated method stub
        return examRepository.exists(examId);
    }

    public Exam findOne(Long examId){
        // TODO Auto-generated method stub
        return examRepository.findOne(examId);
    }

    public RestResponse<Boolean> update(Exam exam){
        // TODO Auto-generated method stub
        Preconditions.checkNotNull(exam, "参数错误");
        Preconditions.checkNotNull(exam.getId(), "参数错误");
        Preconditions.checkNotNull(exam.getTitle(), "参数错误");
        Preconditions.checkNotNull(exam.getContent(), "参数错误");

        Exam examf = findOne(exam.getId());
        Long no = examItemService.countByExamId(exam.getId());

        if (!examf.getJoinNo().equals(exam.getJoinNo()) && no > 0) {
            return RestResponse.error("已经报名无法更改报名人数");
        }

        examf.setTitle(exam.getTitle());
        examf.setContent(exam.getContent());
        examf.setUpdateTime(new DateTime());
        examf.setJoinNo(exam.getJoinNo());

        examRepository.save(examf);

        return RestResponse.ok(true);
    }

    public Exam findByIdAndResTimeLessThanAndExamTimeGreaterThanEqual(
            Long examId){
        // TODO Auto-generated method stub
        DateTime nowTime = new DateTime();
        return examRepository
                .findByIdAndResTimeLessThanAndExamTimeGreaterThanEqual(
                        examId,
                        nowTime,
                        new DateTime(nowTime.getYear(), nowTime
                                .getMonthOfYear(), nowTime.getDayOfMonth(), 0,
                                0, 0));
    }

    public List<Exam> findByResTimeLessThanAndExamTimeGreaterThanEqual(){
        DateTime nowTime = new DateTime();
        return examRepository.findByResTimeLessThanAndExamTimeGreaterThanEqual(
                nowTime,
                new DateTime(nowTime.getYear(), nowTime.getMonthOfYear(),
                        nowTime.getDayOfMonth(), 0, 0, 0));
    }

    public Exam findByIdAndResTimeLessThan(Long examId){
        // TODO Auto-generated method stub
        DateTime nowTime = new DateTime();
        return examRepository.findByIdAndResTimeLessThan(examId, nowTime);
    }

    public void delete(Long id){
        // TODO Auto-generated method stub
        examRepository.delete(id);
        examItemService.deleteByExamId(id);
        examItemStatusService.deleteByExamId(id);
    }

	public void removeLast() {
		// TODO Auto-generated method stub
		examRepository.removeLast();
		examItemService.removeLast();
	}
}
